package com.pzr.soccer.channel.tio;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.pzr.soccer.model.R;
import com.pzr.soccer.util.UserUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.security.jwt.Jwt;
import org.springframework.security.jwt.JwtHelper;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.tio.core.ChannelContext;
import org.tio.core.Tio;
import org.tio.http.common.HttpRequest;
import org.tio.http.common.HttpResponse;
import org.tio.websocket.common.WsRequest;
import org.tio.websocket.common.WsResponse;
import org.tio.websocket.server.handler.IWsMsgHandler;

import java.util.HashMap;
import java.util.Map;

@Component
@Slf4j
public class WebSocketMessageHandler implements IWsMsgHandler {
    /*
     向前端推送的类型
     */
    public static final String Channel_Tag_Pong = "Channel_Tag_Pong";
    public static final String Channel_Tag_ChangedGame = "Channel_Tag_ChangedGame";
    public static final String Channel_Tag_ChangedState="Channel_Tag_ChangedStated";
    public static final String Channel_Tag_PlanMessage="Channel_Tag_PlanMessage";
    public static final String Channel_Tag_SubOrUnSub_Success="Channel_Tag_SubOrUnSub_Success";
    public static final String Channel_Tag_SubOrUnSub_Failed="Channel_Tag_SubOrUnSub_Failed";
    public static final String Channel_Tag_JustText="Channel_Tag_JustText";
    /*
     订阅组
     */
    public static final String Channel_Group_Public="Channel_Group_Public"; //公共组
    public static final String Channel_Group_PlanMessage="Channel_Group_PlanMessage"; //私有组


    /**
     * 处理握手
     *
     * @param httpRequest
     * @param httpResponse
     * @param channelContext
     * @return
     * @throws Exception
     */
    @Override
    public HttpResponse handshake(HttpRequest httpRequest, HttpResponse httpResponse, ChannelContext channelContext) throws Exception {
        String clientIp = httpRequest.getClientIp();
        log.info("开始和{}客户端建立连接", clientIp);
        return httpResponse;
    }

    @Override
    public void onAfterHandshaked(HttpRequest httpRequest, HttpResponse httpResponse, ChannelContext channelContext) throws Exception {
        log.info("和客户端握手成功");
    }

    /**
     * 当前websocket 前端发送一个Bytes 时,我们要做的处理
     *
     * @param wsRequest
     * @param bytes
     * @param channelContext
     * @return
     * @throws Exception
     */
    @Override
    public Object onBytes(WsRequest wsRequest, byte[] bytes, ChannelContext channelContext) throws Exception {
        return null;
    }

    /**
     * 当前端发一个close方时,我们怎么处理
     *
     * @param wsRequest
     * @param bytes
     * @param channelContext
     * @return
     * @throws Exception
     */
    @Override
    public Object onClose(WsRequest wsRequest, byte[] bytes, ChannelContext channelContext) throws Exception {
        Tio.remove(channelContext, "remove channelContext");
        return null;
    }


    /**
     * 当前端发送文本过来
     *
     * @param wsRequest
     * @param text
     * @param channelContext
     * @return
     * @throws Exception
     */
    @Override
    public Object onText(WsRequest wsRequest, String text, ChannelContext channelContext) throws Exception {
        Map<String,Object> map=new HashMap<>();
        Tio.bindGroup(channelContext,Channel_Group_Public); //所有人，订阅一个公共组
        //不是json数据
        if(!text.startsWith("{")){
            map.put("data","hello,接收到你的数据："+text);
            map.put("tag",Channel_Tag_JustText);
            return WsResponse.fromText(JSON.toJSONString(map), "UTF-8");
        }
        JSONObject payload = JSON.parseObject(text);

        String sub = payload.getString("sub"); // 要订阅的组
        //String req = payload.getString("req"); // 当前的request(预留字段)
        String cancel = payload.getString("cancel");// 要取消订阅的组
        //String id = payload.getString("id"); // 订阅的id(预留字段)

        if(!StringUtils.hasText(sub)&&!StringUtils.hasText(cancel)){
            map.put("data","hello,接收到你的数据："+text);
            map.put("tag",Channel_Tag_JustText);
            return WsResponse.fromText(JSON.toJSONString(map), "UTF-8");
        }

        try {
            String username= (String) UserUtil.parserUserFromSecurityContext().get("username");
            if(username==null){
                map.put("data","未有对应用户，订阅失败！");
                map.put("tag",Channel_Tag_SubOrUnSub_Failed);
                return WsResponse.fromText(JSON.toJSONString(map), "UTF-8");
            }
            if(StringUtils.hasText(sub)){
                Tio.bindGroup(channelContext,sub);
            }
            if(StringUtils.hasText(cancel)){
                Tio.unbindGroup(cancel,channelContext);
            }
            map.put("data","处理订阅成功！");
            map.put("tag",Channel_Tag_SubOrUnSub_Success);
            return WsResponse.fromText(JSON.toJSONString(map), "UTF-8");
        }catch (Exception e){
            map.put("data","订阅失败！可能提交数据格式有误");
            map.put("tag",Channel_Tag_SubOrUnSub_Failed);
            return WsResponse.fromText(JSON.toJSONString(map), "UTF-8");
        }

    }
}

